﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Zzcore.Model;
using DnsClient.Internal;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json.Linq;

namespace Zzcore.Controllers
{
    public class PermissionController : BaseController
    {
        private readonly ILogger<PermissionController> _logger;
        public PermissionController(ILogger<PermissionController> logger, IFreeSql fsql) : base(fsql)
        {
            this._logger = logger;
        }

        [HttpPost]
        public async Task<IActionResult> GetUserPermission([FromForm] long uid, [FromForm] string type, [FromForm] long pid)
        {
            type ??= "";
            JArray data = new();
            if (uid == 1)
            {
                // 管理员用户，获取所有菜单
                data = GetAllPermissionTreeData(pid, type).Result;
            }
            else {
                // 其他用户，获取当前用户所有角色
                List<long> rids = await _fsql.Select<RoleUser>().Where(ru => ru.Uid == uid).ToListAsync(ru => ru.Rid);
                if (rids?.Count > 0) {
                    // 获取当前角色的所有ID
                    List<long> pmids = await _fsql.Select<RolePermission>().Where(rp => rids.Contains(rp.Rid)).ToListAsync(rp => rp.Pmid);
                    if (pmids?.Count > 0)
                    {
                        // 去重pmids
                        pmids = pmids.Distinct().ToList();
                        foreach (var pmid in pmids)
                        {
                            await GetAllParentIdByPmid(pmid);
                        }
                        // 该角色所有权限去重
                        allParentPmids = allParentPmids.Distinct().ToList();
                        data = GetRolePermissionTreeData(pid, type).Result;
                    }
                }
            }
            return new JsonResult(new { status = "success", message = "保存成功", code = 1, data });
        }

        List<long> allParentPmids = new(); // 所有权限ID，后面要去重
        [NonAction]
        public async Task GetAllParentIdByPmid(long id)
        {
            // 查询当前节点信息
            Permission permission = await _fsql.Select<Permission>().Where(p => p.Id == id).ToOneAsync();
            if (permission != null)
            {
                allParentPmids.Add(id);
                await GetAllParentIdByPmid(permission.Pid);
            }
        }

        [NonAction]
        public async Task<JArray> GetRolePermissionTreeData(long pid, string type)
        {
            JArray data = new();
            if (type.Equals("menu")) {
                List<Permission> permissions = await _fsql.Select<Permission>().Where(p => p.Pid == pid && p.Type == "menu").Where(p => p.Hidden == 0).Where(p => allParentPmids.Contains(p.Id)).OrderBy("sortid asc").ToListAsync();
                if (permissions != null && permissions.Count > 0)
                {
                    foreach (var permission in permissions)
                    {
                        JObject jo_permission = JObject.FromObject(permission);
                        jo_permission.Add("children", GetRolePermissionTreeData(permission.Id, type).Result);
                        data.Add(jo_permission);
                    }
                }
            } else if (type.Equals("button")) {
                List<Permission> permissions;
                if (pid == 0)
                { // 取所有的权限
                    permissions = await _fsql.Select<Permission>().Where(p => p.Type == "button").Where(p => p.Hidden == 0).Where(p => allParentPmids.Contains(p.Id)).OrderBy("sortid asc").ToListAsync();
                }
                else
                {
                    permissions = await _fsql.Select<Permission>().Where(p => p.Pid == pid && p.Type == "button").Where(p => p.Hidden == 0).Where(p => allParentPmids.Contains(p.Id)).OrderBy("sortid asc").ToListAsync();
                }
                data = JArray.FromObject(permissions);
            } else {
                List<Permission> permissions = await _fsql.Select<Permission>().Where(p => p.Pid == pid).Where(p => p.Hidden == 0).Where(p => allParentPmids.Contains(p.Id)).OrderBy("sortid asc").ToListAsync();
                if (permissions != null && permissions.Count > 0)
                {
                    foreach (var permission in permissions)
                    {
                        JObject jo_permission = JObject.FromObject(permission);
                        jo_permission.Add("children", GetRolePermissionTreeData(permission.Id, type).Result);
                        data.Add(jo_permission);
                    }
                }

            }
            return data;
        }

        [NonAction]
        public async Task<JArray> GetAllPermissionTreeData(long pid, string type)
        {
            JArray data = new();
            if (type.Equals("menu"))
            {
                List<Permission> permissions = await _fsql.Select<Permission>().Where(p => p.Pid == pid && p.Type == "menu").OrderBy("sortid asc").ToListAsync();
                if (permissions != null && permissions.Count > 0)
                {
                    foreach (var permission in permissions)
                    {
                        JObject jo_permission = JObject.FromObject(permission);
                        jo_permission.Add("children", GetAllPermissionTreeData(permission.Id, type).Result);
                        data.Add(jo_permission);
                    }
                }
            }
            else if (type.Equals("button"))
            {
                List<Permission> permissions;
                if (pid == 0)
                { // 取所有的权限
                    permissions = await _fsql.Select<Permission>().Where(p => p.Type == "button").OrderBy("sortid asc").ToListAsync();
                }
                else {
                    permissions = await _fsql.Select<Permission>().Where(p => p.Pid == pid && p.Type == "button").OrderBy("sortid asc").ToListAsync();
                }
                data = JArray.FromObject(permissions);
            }
            else {
                List<Permission> permissions = await _fsql.Select<Permission>().Where(p => p.Pid == pid).OrderBy("sortid asc").ToListAsync();
                if (permissions != null && permissions.Count > 0)
                {
                    foreach (var permission in permissions)
                    {
                        JObject jo_permission = JObject.FromObject(permission);
                        jo_permission.Add("children", GetAllPermissionTreeData(permission.Id, type).Result);
                        data.Add(jo_permission);
                    }
                }
            }
            
            return data;
        }

        [HttpPost]
        public async Task<IActionResult> Save([FromForm] Permission permission)
        {
            long id = await _fsql.Insert<Permission>(permission).ExecuteIdentityAsync();
            permission.Id = id;
            return new JsonResult(new { status = "success", message = "保存成功", code = 1, data = permission });
        }

        [HttpPost]
        public async Task<IDictionary<string, Object>> Delete([FromForm] long id) {
            int affrows = await _fsql.Delete<Permission>().Where(p => p.Id == id).ExecuteAffrowsAsync();
            return RenderJson(data: affrows);
        }

        [HttpPost]
        public async Task<IDictionary<string, Object>> Update([FromForm] Permission permission) {
            int affrows = await _fsql.Update<Permission>().SetSource(permission).ExecuteAffrowsAsync();
            return RenderJson(data: affrows);
        }

        [HttpPost]
        public async Task<IDictionary<string, Object>> Show([FromForm] long id) {
            Permission permission = await _fsql.Select<Permission>().Where(p => p.Id == id).ToOneAsync();
            return RenderJson(data: permission);
        }
    }
}
